#coding=utf-8

import sys
import pika
import time
import uuid

class RbMQconsume(object):

    def __init__(self):
        self.connection = pika.BlockingConnection(pika.ConnectionParameters(host='localhost'))

    def callback(self, ch, method, properties, body):
        print(" [x] Received %r" % body)
        time.sleep( body.count('.'))
        print(" [x] Done")

    def receive_message(self):
        channel = self.connection.channel()

        channel.queue_declare(queue='hello')

        channel.basic_consume(self.callback,
                              queue='hello',
                              no_ack=True)

        print(' [*] Waiting for messages. To exit press CTRL+C')
        channel.start_consuming()

    def safe_callback(self,ch,method,properties,body):
        print " [x] Received %r"%(body)
        time.sleep(body.count('.'))
        print( " [x] done !")
        ch.basic_ack(delivery_tag=method.delivery_tag)

    def safe_receive_message(self):
        channel = self.connection.channel()

        channel.queue_declare(queue='hello',durable=True)
        channel.basic_qos(prefetch_count=1)

        channel.basic_consume(self.safe_callback,
                              queue='hello')

        print(' [*] Waiting for messages. To exit press CTRL+C')
        channel.start_consuming()

    #exchange方法
    def exchange_callback(self,ch,method,properties,body):
        print " [ x ] {}".format(body)

    def receieve_exchange_message(self):
        channel = self.connection.channel()
        channel.exchange_declare(exchange='logs',
                                 type='fanout')
        result = channel.queue_declare(exclusive=True)
        queue_name = result.method.queue
        channel.queue_bind(exchange='logs',queue=queue_name)
        channel.basic_consume(self.exchange_callback,queue=queue_name,no_ack=True)
        channel.start_consuming()
        print(' [*] Waiting for messages. To exit press CTRL+C')

    #direct 方法
    def direct_callback(self, ch, method, properties, body):
        print " [ {} ] {}".format(method.routing_key,body)

    def receieve_direct_message(self):
        channel = self.connection.channel()
        channel.exchange_declare(exchange='direct_logs',
                                 type ='direct')
        result = channel.queue_declare(exclusive=True)
        queue_name = result.method.queue
        severities = ['warning', 'error']
        for severity in severities:
            channel.queue_bind(exchange='direct_logs',
                               queue=queue_name,
                               routing_key=severity)
        channel.basic_consume(self.direct_callback,
                              queue=queue_name,
                              no_ack=True)
        channel.start_consuming()

    #topic
    def topic_callback(self, ch, method, properties, body):
        print " [ {} ] {}".format(method.routing_key, body)

    def receieve_topic_message(self):
        channel = self.connection.channel()
        channel.exchange_declare(exchange='topic_logs',
                                 type='topic')

        result = channel.queue_declare(exclusive=True)
        queue_name = result.method.queue
        binding_keys = ["anonymous.info","lck.info","lck.error"]
        binding_key = 'lck.*'
        channel.queue_bind(exchange='topic_logs',
                           queue=queue_name,
                           routing_key=binding_key)
        channel.basic_consume(self.topic_callback,
                              queue= queue_name,
                              no_ack=True)
        channel.start_consuming()

    #rpc
    def rpc_callback(self,ch,method,props,body):
        if self.corr_id == props.correlation_id:
            self.response = body

    def receieve_rpc_message(self,n):
        channel = self.connection.channel()
        result = channel.queue_declare(exclusive=True)
        callback_queue = result.method.queue
        channel.basic_consume(self.rpc_callback,
                              no_ack=True,
                              queue=callback_queue)

        self.response = None
        self.corr_id = str(uuid.uuid4())
        channel.basic_publish(exchange='',
                              routing_key='rpc_queue',
                              properties=pika.BasicProperties(reply_to=callback_queue,correlation_id=self.corr_id),
                              body=str(n))
        while self.response is None:
            self.connection.process_data_events()
        return int(self.response)


    def __del__(self):
        self.connection.close()


if  __name__=="__main__":
    rqconsume = RbMQconsume()
    # rqconsume.safe_receive_message()
    # rqconsume.receieve_exchange_message()

    # rqconsume.receieve_direct_message()
    # rqconsume.receieve_topic_message()
    print rqconsume.receieve_rpc_message(30)